﻿using System;
using System.Drawing;
using System.Drawing.Drawing2D;
using System.Drawing.Imaging;
using System.IO;
using System.Web;

namespace UsefulClasses
{
    public static class ImageController
    {
        public static System.Drawing.Image ResizeMyImage(System.Drawing.Image image, Size newSize)
        {
            Bitmap newImage = new Bitmap(newSize.Width, newSize.Height);
            using (Graphics gr = Graphics.FromImage(newImage))
            {
                gr.SmoothingMode = SmoothingMode.HighQuality;
                gr.InterpolationMode = InterpolationMode.HighQualityBicubic;
                gr.PixelOffsetMode = PixelOffsetMode.HighQuality;
                gr.DrawImage(image, new Rectangle(0, 0, newSize.Width, newSize.Height));
            }

            return newImage;
        }

        public static byte[] ResizeMyImage(byte[] image, Size newSize)
        {
            Bitmap newImage = new Bitmap(newSize.Width, newSize.Height);
            using (Graphics gr = Graphics.FromImage(newImage))
            {
                gr.SmoothingMode = SmoothingMode.HighQuality;
                gr.InterpolationMode = InterpolationMode.HighQualityBicubic;
                gr.PixelOffsetMode = PixelOffsetMode.HighQuality;
                gr.DrawImage(GetImageFromByteArray(image), new Rectangle(0, 0, newSize.Width, newSize.Height));
            }

            return GetByteArrayFromImage(newImage);
        }

        public static byte[] GetByteArrayFromImage(System.Drawing.Image image)
        {
            MemoryStream ms = new MemoryStream();
            image.Save(ms, System.Drawing.Imaging.ImageFormat.Gif);
            return ms.ToArray();
        }

        public static System.Drawing.Image GetImageFromByteArray(byte[] image)
        {
            MemoryStream ms = new MemoryStream(image);
            Image returnImage = Bitmap.FromStream(ms);
            return returnImage;
        }

        public static System.Drawing.Image PerformASPImageUpload(HttpPostedFile file, HttpServerUtility server, string folder)
        {
            string FileName = file.FileName;
            string saveFile = server.MapPath(folder + ((folder.Replace("/", "\\").EndsWith("\\")) ? "" : "\\") + UsefulClasses.StringManipulation.GenerateRandomString(25) + "." + FileName.Split('.')[FileName.Split('.').Length - 1]);

            if (validateFolderExistance(saveFile))
            {
                file.SaveAs(saveFile);
                System.Drawing.Image IMG = System.Drawing.Image.FromFile(saveFile);

                try
                {
                    File.Delete(saveFile);
                }
                catch { }

                return IMG;
            }

            return null;
        }
        
        public static string PerformASPFileUpload(HttpPostedFile file, HttpServerUtility server, string folder)
        {
            string FileName = file.FileName;
            string newFIleName = UsefulClasses.StringManipulation.GenerateRandomString(25) + "." + FileName.Split('.')[FileName.Split('.').Length - 1];
            string saveFile = server.MapPath(folder + ((folder.Replace("/", "\\").EndsWith("\\")) ? "" : "\\") + newFIleName);

            if (validateFolderExistance(saveFile))
            {
                file.SaveAs(saveFile);

                return newFIleName;
            }

            return string.Empty;
        }

        private static bool validateFolderExistance(string file)
        {
            try
            {
                string newFile = file.Split('\\')[0] + "\\";

                for (int i = 1; i < file.Split('\\').Length - 1; i++)
                {
                    newFile += file.Split('\\')[i] + "\\";

                    if (!Directory.Exists(newFile))
                        Directory.CreateDirectory(newFile);
                }

                return true;
            }
            catch
            { }

            return false;
        }

        public static string ToBase64String(this Bitmap bmp, ImageFormat imageFormat)
        {
            string base64String = string.Empty;

            MemoryStream memoryStream = new MemoryStream();
            bmp.Save(memoryStream, imageFormat);

            memoryStream.Position = 0;
            byte[] byteBuffer = memoryStream.ToArray();

            memoryStream.Close();

            base64String = Convert.ToBase64String(byteBuffer);
            byteBuffer = null;

            return base64String;
        }

        public static string GetHtmlImage(this Bitmap bmp, ImageFormat imageFormat, bool ImgWithAndHeight, HtmlAttribute[] attributes)
        {
            string imgTag = string.Empty;
            string base64String = string.Empty;

            base64String = bmp.ToBase64String(imageFormat);

            imgTag = "<img src=\"data:image/" + imageFormat.ToString() + ";base64,";
            imgTag += base64String + "\" ";
            if (ImgWithAndHeight)
            {
                imgTag += "width=\"" + bmp.Width.ToString() + "\" ";
                imgTag += "height=\"" + bmp.Height.ToString() + "\" />";
            }

            foreach (HtmlAttribute attr in attributes)
            {
                if (!ImgWithAndHeight || (attr.Name.ToUpper() != "WIDTH" && attr.Name.ToUpper() != "HEIGHT"))
                    imgTag += attr.Name + "=\"" + attr.Name.Replace('"', '`') + "\" ";
            }

            return imgTag;
        }

        public static Bitmap GenerateProfileNameImage(string text, int width, int height, string fontFamily, Color foreColour, Color backColour)
        {
            Random random = new Random();

            // Create a new 32-bit bitmap image.
            Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb);

            // Create a graphics object for drawing.
            Graphics g = Graphics.FromImage(bitmap);
            g.SmoothingMode = SmoothingMode.AntiAlias;
            Rectangle rect = new Rectangle(0, 0, width, height);

            // Fill in the background.
            //HatchBrush hatchBrush = new HatchBrush(HatchStyle.no, Color.LightGray, Color.White);
            SolidBrush myBrush = new SolidBrush(backColour);
            g.FillRectangle(myBrush, rect);

            // Set up the text font.
            SizeF size;
            float fontSize = rect.Height + 1;
            Font font;
            StringFormat format = new StringFormat();
            format.Alignment = StringAlignment.Center;
            format.LineAlignment = StringAlignment.Center;

            // Adjust the font size until the text fits within the image.
            do
            {
                fontSize--;
                font = new Font(fontFamily, fontSize, FontStyle.Bold);
                size = g.MeasureString(text, font, new SizeF(width, height), format);
            } while (size.Width > rect.Width && size.Height > rect.Height);

            // Create a path using the text and warp it randomly.
            GraphicsPath path = new GraphicsPath();
            path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format);
            //float v = 4F;
            //PointF[] points =
            //{
            //    new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v),
            //    new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v),
            //    new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v),
            //    new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v)
            //};
            //Matrix matrix = new Matrix();
            //matrix.Translate(0F, 0F);
            //path.Warp(points, rect, matrix, WarpMode.Perspective, 0F);

            // Draw the text.
            //HatchBrush hatchBrush = new HatchBrush(HatchStyle.DashedUpwardDiagonal, Color.DarkGray, Color.Black);
            myBrush = new SolidBrush(foreColour);
            g.FillPath(myBrush, path);

            // Clean up.
            font.Dispose();
            myBrush.Dispose();
            g.Dispose();

            return bitmap;
        }
    }

    public class HtmlAttribute
    {
        public string Name { get; set; }
        public string Value { get; set; }
    }
}
